home *** CD-ROM | disk | FTP | other *** search
/ BCI NET 2 / BCI NET 2.iso / archives / programming / asm / adisv1_3.lha / src / amiga.c next >
Encoding:
C/C++ Source or Header  |  1993-09-24  |  7.4 KB  |  266 lines

  1. /*
  2.  * Change history
  3.  * $Log:    amiga.c,v $
  4.  * Revision 3.0  93/09/24  17:52:53  Martin_Apel
  5.  * New feature: Added extra 68040 FPU opcodes
  6.  * 
  7.  * Revision 2.3  93/07/18  22:55:33  Martin_Apel
  8.  * *** empty log message ***
  9.  * 
  10.  * Revision 2.2  93/07/13  11:39:26  Martin_Apel
  11.  * Bug fix: user_aborted_analysis now resets CTRL-D signal upon abortion
  12.  * 
  13.  * Revision 2.1  93/07/08  20:46:06  Martin_Apel
  14.  * *** empty log message ***
  15.  * 
  16.  * Revision 2.0  93/07/01  11:53:34  Martin_Apel
  17.  * *** empty log message ***
  18.  * 
  19.  * Revision 1.5  93/06/06  00:07:25  Martin_Apel
  20.  * Major mod.: Added support for library/device disassembly (option -dl)
  21.  * 
  22.  * Revision 1.4  93/06/03  18:20:27  Martin_Apel
  23.  * Minor mod.: Remove temporary files upon exit (even with CTRL-C)
  24.  * 
  25.  */
  26.  
  27. static char rcsid [] = "$Id: amiga.c,v 3.0 93/09/24 17:52:53 Martin_Apel Exp $";
  28.  
  29. #include <exec/types.h>
  30. #include "defs.h"
  31.  
  32. #ifdef AMIGA
  33. #include <exec/resident.h>
  34. #include <dos/dos.h>
  35. #include <clib/exec_protos.h>
  36. #include <clib/dos_protos.h>
  37.  
  38. /******************************************************************/
  39.  
  40. BOOL user_aborted_analysis ()
  41.  
  42. {
  43. if (SetSignal (0L, SIGBREAKF_CTRL_D) & SIGBREAKF_CTRL_D)
  44.   {
  45.   fprintf (stderr, "Analysis aborted...\n");
  46.   return (TRUE);
  47.   }
  48. return (FALSE);
  49. }
  50.  
  51. /******************************************************************/
  52.  
  53. void delete_tmp_files ()
  54.  
  55. {
  56. char command [40];
  57.  
  58. /* See hunks.c for generation of tmp file name */
  59. sprintf (command, "delete %s%lx#? >nil:", TMP_FILENAME, ¤t_address);
  60. Execute ((UBYTE*)command, NULL, NULL);
  61. }
  62.  
  63. /******************************************************************/
  64.  
  65. static void mark_as_long (void *address)
  66.  
  67. {
  68. /**********************************************************************/
  69. /*     Address points into the code area. mark_as_long marks the      */
  70. /*     corresponding place in the flags array as data. If written     */
  71. /*        directly into disasm_as_lib, it clutters up the code        */
  72. /**********************************************************************/
  73.  
  74. *((ULONG*)(flags + ((UBYTE*)address - (UBYTE*)code))) |=
  75.       TMP_DATA | (TMP_DATA << 8) | (TMP_DATA << 16) | (TMP_DATA << 24);
  76. }
  77.  
  78. /******************************************************************/
  79.  
  80. static void mark_as_word (void *address)
  81.  
  82. {
  83. *((UWORD*)(flags + ((UBYTE*)address - (UBYTE*)code))) |= 
  84.      TMP_DATA | (TMP_DATA << 8);
  85. }
  86.  
  87. /******************************************************************/
  88.  
  89. static void process_func_table_l (ULONG *func_table, UBYTE type)
  90.  
  91. {
  92. int i;
  93. char label_name [20];
  94.  
  95. enter_ref (*func_table,       "Open", ACC_CODE);    mark_as_long (func_table);
  96. enter_ref (*(func_table + 1), "Close", ACC_CODE);   mark_as_long (func_table + 1);
  97. enter_ref (*(func_table + 2), "Expunge", ACC_CODE); mark_as_long (func_table + 2);
  98. enter_ref (*(func_table + 3), "Null", ACC_CODE);    mark_as_long (func_table + 3);
  99.  
  100. if (type == NT_DEVICE)
  101.   { 
  102.   enter_ref (*(func_table + 4), "BeginIO", ACC_CODE);
  103.   mark_as_long (func_table + 4);
  104.   enter_ref (*(func_table + 5), "AbortIO", ACC_CODE);
  105.   mark_as_long (func_table + 5);
  106.   }
  107. else
  108.   {
  109.   for (i = 4; *(func_table + i) != 0xffffffff; i++)
  110.     {
  111.     sprintf (label_name, "Func%d", i - 4);
  112.     enter_ref (*(func_table + i), label_name, ACC_CODE);
  113.     mark_as_long (func_table + i);
  114.     }
  115.   }
  116. }
  117.  
  118. /******************************************************************/
  119.  
  120. static void process_func_table_w (UWORD *func_table, UBYTE type)
  121.  
  122. {
  123. int i;
  124. char label_name [20];
  125. /* relative to start of function table */
  126. ULONG base = (ULONG)((UBYTE*)func_table - (UBYTE*)code) - 2 + first_address;
  127.  
  128. enter_ref (base + *func_table,       "Open", ACC_CODE);
  129. mark_as_word (func_table);
  130. enter_ref (base + *(func_table + 1), "Close", ACC_CODE);   
  131. mark_as_word (func_table + 1);
  132. enter_ref (base + *(func_table + 2), "Expunge", ACC_CODE); 
  133. mark_as_word (func_table + 2);
  134. enter_ref (base + *(func_table + 3), "Null", ACC_CODE);    
  135. mark_as_word (func_table + 3);
  136.  
  137. if (type == NT_DEVICE)
  138.   { 
  139.   enter_ref (base + *(func_table + 4), "BeginIO", ACC_CODE);
  140.   mark_as_word (func_table + 4);
  141.  
  142.   enter_ref (base + *(func_table + 5), "Abort", ACC_CODE);
  143.   mark_as_word (func_table + 5);
  144.   }
  145. else
  146.   {
  147.   for (i = 4; *(func_table + i) != 0xffff; i++)
  148.     {
  149.     sprintf (label_name, "Func%d", i - 4);
  150.     enter_ref (base + *(func_table + i), label_name, ACC_CODE);
  151.     mark_as_word (func_table + i);
  152.     }
  153.   }
  154. }
  155.  
  156. /******************************************************************/
  157.  
  158. BOOL add_lib_labels (UWORD *code_seg)
  159.  
  160. {
  161. /*
  162. The  first  code  hunk  has  been read in.  We expect to find a ROMTag
  163. structure at the start of the segment.
  164. */
  165. UWORD *code_ptr;
  166. struct Resident *LibHeader;
  167. UBYTE type;
  168. ULONG *data_table,
  169.       *func_table,
  170.       *init_table;
  171. ULONG i;
  172.  
  173. code = code_seg;
  174. for (code_ptr = code_seg, current_address = first_address; 
  175.      *code_ptr != RTC_MATCHWORD && current_address < last_address;
  176.      code_ptr++, current_address += 2);
  177.  
  178. if (*code_ptr != RTC_MATCHWORD)
  179.   return (FALSE);
  180.  
  181. LibHeader = (struct Resident*)code_ptr;
  182. if ((ULONG)LibHeader->rt_MatchTag != current_address)
  183.   return (FALSE);
  184.  
  185. /* Mark ROMTag structure as data */
  186.  
  187. for (i = 0; i < sizeof (struct Resident); i++)
  188.   *(flags + current_address - first_address + i) |= TMP_DATA;
  189.  
  190. type = LibHeader->rt_Type;
  191. enter_ref (current_address, "ROMTag", (UWORD)(ACC_DATA | ACC_WORD));
  192. enter_ref (current_address + (long)&(LibHeader->rt_Flags) - (long)LibHeader, 
  193.            "Flags", (UWORD)(ACC_DATA | ACC_BYTE));
  194. enter_ref (current_address + (long)&(LibHeader->rt_Version) - (long)LibHeader, 
  195.            "Version", (UWORD)(ACC_DATA | ACC_BYTE));
  196. enter_ref (current_address + (long)&(LibHeader->rt_Type) - (long)LibHeader, 
  197.            "Type", (UWORD)(ACC_DATA | ACC_BYTE));
  198. enter_ref (current_address + (long)&(LibHeader->rt_Pri) - (long)LibHeader, 
  199.            "Pri", (UWORD)(ACC_DATA | ACC_BYTE));
  200. enter_ref (current_address + (long)&(LibHeader->rt_Name) - (long)LibHeader, 
  201.            "Name", (UWORD)(ACC_DATA | ACC_LONG));
  202. enter_ref (current_address + (long)&(LibHeader->rt_IdString) - (long)LibHeader,
  203.            "IdString", (UWORD)(ACC_DATA | ACC_LONG));
  204. if (!(LibHeader->rt_Flags & RTF_AUTOINIT))
  205.   {
  206.   /* rt_Init points to init routine */
  207.   enter_ref ((ULONG)LibHeader->rt_Init, "Init", ACC_CODE);
  208.   save_flags ();
  209.   return (TRUE);
  210.   }
  211.  
  212. /* 
  213. rt_Init points to data structure. The second longword is a pointer to
  214. a function table, the third a pointer to a data table, and the fourth
  215. a pointer to an init routine
  216. */
  217. init_table = (ULONG*)((UBYTE*)code_seg + (long)(LibHeader->rt_Init) 
  218.                - first_address);
  219. mark_as_long (init_table);
  220. mark_as_long (init_table + 1);
  221. mark_as_long (init_table + 2);
  222. mark_as_long (init_table + 3);
  223. enter_ref (*(init_table + 3), "Init", ACC_CODE);
  224.  
  225. /* Maybe func_table is zero */
  226. if (IS_RELOCATED ((ULONG)LibHeader->rt_Init + 4))
  227.   {
  228.   func_table = (ULONG*)((UBYTE*)code_seg + *(init_table + 1) - first_address);
  229.   if (*((UWORD*)func_table) == 0xffff)
  230.     process_func_table_w (((UWORD*)func_table) + 1, type);
  231.   else
  232.     process_func_table_l (func_table, type);
  233.   }
  234.  
  235. /* Maybe data_table is zero */
  236. if (IS_RELOCATED ((ULONG)LibHeader->rt_Init + 8))
  237.   {
  238.   /* It's quite difficult to find the end of the data table without
  239.      using InitStruct. So I just mark the first word as data and
  240.      leave the rest to the analysis pass */
  241.   data_table = (ULONG*)((UBYTE*)code_seg + *(init_table + 2) - first_address);
  242.   mark_as_word (data_table);
  243.   }
  244.  
  245. save_flags ();
  246. return (TRUE);
  247. }
  248.  
  249. #else
  250.  
  251.  
  252. BOOL user_aborted_analysis ()
  253.  
  254. {
  255. return (FALSE);
  256. }
  257.  
  258. /******************************************************************/
  259.  
  260. void delete_tmp_files ()
  261.  
  262. {
  263. }
  264.  
  265. #endif
  266.